package javaCode.chapter09.innerclass;

/**
 * 演示匿名内部类的使用
 */
public class AnonymousInnerClass {
    public static void main(String[] args) {

        Outer04 outer04 = new Outer04();
        outer04.method();
    }
}

class Outer04{ //外部类
    private int n1 = 10;
    public void method() { //方法
        //解读
        //1. 需求：想使用IA接口，并创建对象
        //2. 传统方式，是写一个类，实现该接口，并创建对象
        //3. 需求是 Tiger/Dog 类只使用一次，后面不再使用
        //4. 可以使用匿名内部类简化开发
        //5. tiger的编译类型 ? IA
        //6. tiger的运行类型 ? 就是匿名内部类 XXX ==> Outer04$1
        /*
            我们看底层 会分配 类名 Outer04$1
            class Outer04$1 implements IA{
                @Override
                public void cry() {
                    System.out.println("老虎叫唤...");
                }
            }
         */
        //7. jdk底层在创建匿名内部类 Outer04$1，立即马上就创建了 Outer04$1实例，并且把地址返回给 tiger
        //8. 匿名内部类使用一次，就不能再使用了
        IA tiger = new IA() {
            @Override
            public void cry() {
                System.out.println("老虎叫唤...");
            }
        };
        System.out.println("tiger的运行类型=" + tiger.getClass());
        tiger.cry();

        //演示基于内部类的匿名内部类
        //分析
        //1. father的编译类型 Father
        //2. father的运行类型 匿名内部类 Outer$2
        //3. 底层会创建匿名内部类
        /*
            class Cuter extends Father{
            }
         */
        //4. 同时也直接返回了 匿名内部类 Outer$2的对象
        //5. 注意("jack") 参数列表会传递给 构造器
        Father father = new Father("jack"){
            @Override
            public void test(){
                    System.out.println("匿名内部类重写了test方法");
            }
        };
        System.out.println("father的运行类型=" + father.getClass());
        father.test();
    }
}

interface IA{ //接口
    public void cry();
}

class Father{
    public Father(String name){
        System.out.println("接收到的name=" + name);
    }

    public void test(){

    }
}